﻿#include <stdexcept>
#include "./TesMath/TesLineInterpolation.h"


TesLineInterpolation::TesLineInterpolation()
{
    Reset();
}

void TesLineInterpolation::SetPoints(const std::vector<TesVector3>& points)
{
    //如果点数小于2就直接抛异常
    if (points.size() < 2)
        throw std::logic_error("points count can't less than 2!");

    //这里需要重置
    Reset();

    //循环处理点生成线段
    float curDistance = 0.0f;
    for (size_t i = 1; i < points.size(); i++)
    {
        float dis = (points[i] - points[i - 1]).Length();
        Internal data = {};
        data.start = curDistance;
        data.distance = dis;
        data.line = TesLinespace<TesVector3>(points[i - 1], points[i], dis);
        datas.push_back(data);
        curDistance += dis;
    }
}

TesVector3 TesLineInterpolation::GetPoint(float distance)
{
    //如果是正向找点
    if (distance >= datas[findIdx].start)
    {
        //向前找到正确的线段
        while(distance < datas[findIdx].start || distance > (datas[findIdx].start + datas[findIdx].distance))
            findIdx++;
    }
    else
    {
        //反向找到正确的线段
        while(distance < datas[findIdx].start || distance > (datas[findIdx].start + datas[findIdx].distance))
            findIdx--;
    }
        
    //获取插值
    lastPos = distance;
    distance -= datas[findIdx].start;   //长度是相对的所以这里需要减一截
    return datas[findIdx].line.GetValue(distance);
}

bool TesLineInterpolation::IsEnd()
{
    if (findIdx == datas.size() - 1 && lastPos >= datas.back().start + datas.back().distance)
        return true;

    return false;
}

float TesLineInterpolation::Length()
{
    Internal& last = datas.back();
    return last.start + last.distance;
}

void TesLineInterpolation::Reset()
{
    findIdx = 0;
    lastPos = 0.0f;
}